#include "GLHeaders.hpp"
#include "ReferenceCube.hpp"

#include <iostream>

void ReferenceCube_::Draw(void){
  glBindBuffer(GL_ARRAY_BUFFER, cube_buffers[0]);
  glNormalPointer(GL_FLOAT, 9 * sizeof(GLfloat), 0);
  glColorPointer(3, GL_FLOAT, 9 * sizeof(GLfloat), ((GLfloat*)NULL+(3)));
  glVertexPointer(3, GL_FLOAT, 9 * sizeof(GLfloat), ((GLfloat*)NULL+(6)));

  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, cube_buffers[1]);

  glEnableClientState(GL_NORMAL_ARRAY);
  glEnableClientState(GL_COLOR_ARRAY);
  glEnableClientState(GL_VERTEX_ARRAY);

  glDrawElements(GL_TRIANGLES, 36, GL_UNSIGNED_INT, 0);

  glDisableClientState(GL_NORMAL_ARRAY);
  glDisableClientState(GL_COLOR_ARRAY);
  glDisableClientState(GL_VERTEX_ARRAY);
}

ReferenceCube_::ReferenceCube_(void){ 
  GLfloat cube_array_tmp[216] = {//NORMAL, COLOR, VERTEX
    // Front Face
    0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,-0.5f,-0.5f, 0.5f,
    0.0f, 0.0f, 1.0f, 1.0f, 0.0f, 1.0f, 0.5f,-0.5f, 0.5f,
    0.0f, 0.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.5f, 0.5f, 0.5f,
    0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 1.0f,-0.5f, 0.5f, 0.5f,
    // Right Face
    1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.5f,-0.5f, 0.5f,
    1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.5f,-0.5f,-0.5f,
    1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, 0.5f, 0.5f,-0.5f, 
    1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, 0.5f, 0.5f, 0.5f,
    // Back Face
    0.0f, 0.0f,-1.0f, 1.0f, 0.0f, 0.0f, 0.5f,-0.5f,-0.5f,
    0.0f, 0.0f,-1.0f, 0.0f, 0.0f, 0.0f,-0.5f,-0.5f,-0.5f,
    0.0f, 0.0f,-1.0f, 0.0f, 1.0f, 0.0f,-0.5f, 0.5f,-0.5f,
    0.0f, 0.0f,-1.0f, 1.0f, 1.0f, 0.0f, 0.5f, 0.5f,-0.5f,
    // Left Face
    -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,-0.5f,-0.5f,-0.5f,
    -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f,-0.5f,-0.5f, 0.5f,
    -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 1.0f,-0.5f, 0.5f, 0.5f,
    -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f,-0.5f, 0.5f,-0.5f,
    // Under Face
    0.0f,-1.0f, 0.0f, 0.0f, 0.0f, 0.0f,-0.5f,-0.5f,-0.5f,
    0.0f,-1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.5f,-0.5f,-0.5f,
    0.0f,-1.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.5f,-0.5f, 0.5f,
    0.0f,-1.0f, 0.0f, 0.0f, 0.0f, 1.0f,-0.5f,-0.5f, 0.5f,
    // Top Face
    0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f,-0.5f, 0.5f, 0.5f,
    0.0f, 1.0f, 0.0f, 1.0f, 1.0f, 1.0f, 0.5f, 0.5f, 0.5f,
    0.0f, 1.0f, 0.0f, 1.0f, 1.0f, 0.0f, 0.5f, 0.5f,-0.5f,
    0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f,-0.5f, 0.5f,-0.5f
  };

  GLuint indice_array_tmp[36] = {
    1,  2,  0,  0,  2,  3,
    5,  6,  4,  4,  6,  7,
    9, 10,  8,  8, 10, 11,
    13, 14, 12, 12, 14, 15,
    17, 18, 16, 16, 18, 19,
    21, 22, 20, 20, 22, 23
  };

  cube_array = (GLfloat *) new GLfloat[216];
  indice_array = (GLuint *) new GLuint[36];

  for(int i=0; i < 216; i++)
    cube_array[i] = cube_array_tmp[i];
   for(int i=0; i < 36; i++)
    indice_array[i] = indice_array_tmp[i];

  cube_buffers = new GLuint[2];
  glGenBuffers( 2, cube_buffers);

  glBindBuffer(GL_ARRAY_BUFFER, cube_buffers[0]);
  glBufferData(GL_ARRAY_BUFFER, sizeof(cube_array)*216, cube_array, GL_STATIC_DRAW);

  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, cube_buffers[1]);
  glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indice_array)*36, indice_array, GL_STATIC_DRAW);
}

ReferenceCube_::~ReferenceCube_(void){
  glDeleteBuffers(2, cube_buffers);
  delete[] cube_array;
  delete[] indice_array;
  delete[] cube_buffers;
}
